package cn.iocoder.yudao.module.movie.serive.movieInf;

import cn.hutool.core.net.url.UrlBuilder;
import cn.hutool.core.util.StrUtil;
import cn.hutool.http.Header;
import cn.hutool.http.HttpRequest;
import cn.hutool.http.HttpResponse;
import cn.iocoder.yudao.framework.common.exception.ServiceException;
import cn.iocoder.yudao.module.movie.api.domain.CityDO;
import cn.iocoder.yudao.module.movie.api.domain.MovieCinemasDO;
import cn.iocoder.yudao.module.movie.api.params.MovieCinemaParamDO;
import cn.iocoder.yudao.module.movie.enums.MovieInfEnum;
import cn.iocoder.yudao.module.movie.pojo.YouPiaoPiaoDTO;
import cn.iocoder.yudao.module.movie.api.domain.MovieListDO;
import cn.iocoder.yudao.module.movie.pojo.convert.MoviesConvert;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.util.Assert;

import javax.validation.constraints.NotNull;
import javax.validation.constraints.Null;
import java.util.List;
import java.util.stream.Collectors;

/**
 * <p>  </p>
 */
@Service
@Slf4j
public class YouPiaoPiaoMovieInfServiceImpl implements MovieInfService {
    private final String host = "https://apicore.youpiaopiao.cn";

    /**
     * 获取电影接口信息类型
     *
     * @return
     */
    @Override
    public MovieInfEnum getMovieInfType() {
        return MovieInfEnum.YOU_PIAO_PIAO;
    }

    /**
     * 获取热映电影
     *
     * @param cityId 城市id
     * @return 热映电影
     */
    @Override
    public MovieListDO getMovies(String cityId) {
        YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies> movies = getMovies(cityId, 100, 0);
        // 访问失败
        if (movies == null || movies.getCode() != 0) {
            throw new ServiceException(1002, "获取热门电影失败，请联系客服");
        }
        return MoviesConvert.convert(movies.getData());
    }

    /**
     * 获取即将上映电影
     *
     * @param cityId 城市id
     * @return 即将上映电影
     */
    @Override
    public MovieListDO getComingMovies(String cityId) {
        YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies> res = this.getComingMovies(cityId, 100, 0);
        if (res == null || res.getCode() != 0) {
            throw new ServiceException(1004, "获取即将上映电影失败，请联系客服");
        }
        return MoviesConvert.convert(res.getData());
    }

    /**
     * 获取城市列表
     *
     * @return 城市列表
     */
    @Override
    public List<CityDO> getCityList() {
        YouPiaoPiaoDTO<List<YouPiaoPiaoDTO.City>> res = this.getCitys();
        if (res == null || res.getCode() != 0) {
            throw new ServiceException(1003, "获取城市列表失败，请联系客服");
        }
        List<YouPiaoPiaoDTO.City> cityList = res.getData();
        return cityList.stream().map(MoviesConvert::convert).collect(Collectors.toList());
    }

    @Override
    public MovieCinemasDO getMovieCinemas(MovieCinemaParamDO paramDO) {
        YouPiaoPiaoDTO<YouPiaoPiaoDTO.MovieCinemas> res = this.getMovieCinemas(
                "1",
                paramDO.getCityId(),
                paramDO.getMovieId(),
                StrUtil.nullToDefault(paramDO.getDay(), ""),
                StrUtil.nullToDefault(paramDO.getDistrictId(), ""),
                StrUtil.nullToDefault(paramDO.getBrandId(), ""),
                StrUtil.nullToDefault(paramDO.getLat(), ""),
                StrUtil.nullToDefault(paramDO.getLng(), ""),
                "QMM"
        );
        if (res == null || res.getCode() != 0) {
            throw new ServiceException(1005, "获取影院列表失败，请联系客服");
        }
        return MoviesConvert.convert(res.getData());
    }

    /**
     * 获取影院排片列表
     *
     * @param movieId
     * @param cinemaId
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaShows> getCinemaShows(@Null String movieId, @NotNull String cinemaId) {
        String url = UrlBuilder.of(host + "/api/movies/cinema_shows")
                .addQuery("movieId", movieId)
                .addQuery("cinemaId", cinemaId)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取影院排片列表】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaShows>>() {
        });
    }

    /**
     * 获取电影的影院列表
     *
     * @param cityId 城市id
     * @param movieId 电影id
     * @param day 日期
     * @param districtId 区域id
     * @param brandId 品牌id
     * @param lat 纬度
     * @param lng 经度
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.MovieCinemas> getMovieCinemas(@NotNull String type,
                                                                       @NotNull String cityId,
                                                                       @NotNull String movieId,
                                                                       @NotNull  String day,
                                                                       @NotNull String districtId,
                                                                       @NotNull String brandId,
                                                                       @NotNull String lat,
                                                                       @NotNull String lng,
                                                                       @NotNull String sid) {
        String url = UrlBuilder.of(host + "/api/movies/movie_cinemas")
                .addQuery("type", type)
                .addQuery("movieId", movieId)
                .addQuery("city", cityId)
                .addQuery("day", day)
                .addQuery("districtId", districtId)
                .addQuery("brandId", brandId)
                .addQuery("lat", lat)
                .addQuery("lng", lng)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取电影的影院列表】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.MovieCinemas>>() {
        });
    }
    /**
     * 获取电影场次（座位）详情
     *
     * @param sessionId
     * @param movieId
     * @param cinemaId
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaShows> getCinemaSession(@NotNull String sessionId, @NotNull String movieId, @NotNull String cinemaId) {
        String url = UrlBuilder.of(host + "/api/movies/session")
                .addQuery("movieId", movieId)
                .addQuery("cinemaId", cinemaId)
                .addQuery("sessionId", sessionId)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取电影场次（座位）详情】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaShows>>() {
        });
    }
    /**
     * 获取影院列表
     *
     * @param cityId
     * @param districtId
     * @param brandId
     * @param lat
     * @param lng
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.Cinemas> getCinema(@Null String cityId,
                                                            @Null String districtId,
                                                            @Null String brandId,
                                                            @Null Integer lat,
                                                            @Null Integer lng) {
        String url = UrlBuilder.of(host + "/api/movies/cinemas")
                .addQuery("cityId", cityId)
                .addQuery("districtId", districtId)
                .addQuery("brandId", brandId)
                .addQuery("lat", lat)
                .addQuery("lng", lng)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取影院列表】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.Cinemas>>() {
        });
    }
    /**
     * 获取影院筛选条件
     *
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaFilter> getCinemaFilter(@NotNull String cityId) {
        Assert.notNull(cityId, "cityId不能为空");
        String url = UrlBuilder.of(host + "/api/movies/cinema_filter")
                .addQuery("cityId", cityId)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取影院筛选条件】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.CinemaFilter>>() {
        });
    }
    /**
     * 获取城市列表
     *
     * @return
     */
    public YouPiaoPiaoDTO<List<YouPiaoPiaoDTO.City>> getCitys() {
        String url = UrlBuilder.of(host + "/api/movies/get_citys")

                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取城市列表】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<List<YouPiaoPiaoDTO.City>>>() {
        });
    }
    /**
     * 获取热门电影列表 相同城市的访问可以加缓存
     *
     * @param cityId 城市id
     * @param pageSize 可选
     * @param pageIndex 页码 从0开始
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies> getMovies(String cityId, Integer pageSize, Integer pageIndex) {
        String url = UrlBuilder.of(host + "/api/movies/movies")
                .addQuery("cityId", cityId)
                .addQuery("pageSize", pageSize)
                .addQuery("pageIndex", pageIndex)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取热门电影】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies>>() {
        });
    }
    /**
     * 获取即将上映电影 相同城市的访问可以加缓存
     *
     * @param cityId 城市id
     * @param pageSize 可选
     * @param pageIndex 页码 从0开始
     * @return
     */
    public YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies> getComingMovies(String cityId, Integer pageSize, Integer pageIndex) {
        String url = UrlBuilder.of(host + "/api/movies/coming_movies")
                .addQuery("cityId", cityId)
                .addQuery("pageSize", pageSize)
                .addQuery("pageIndex", pageIndex)
                .build();
        HttpResponse execute = this.buildRequest(HttpRequest.get(url))
                .execute();
        String body = execute.body();
        log.info("【获取即将上映电影】url:{},body:{}", url, body);
        return JSONObject.parseObject(body, new TypeReference<YouPiaoPiaoDTO<YouPiaoPiaoDTO.Movies>>() {
        });
    }

    private HttpRequest buildRequest(HttpRequest request) {
        return request.header("AppId", "wxc728fd458500c668")
                .header("EntId", "1000")
                .header(Header.HOST, "apicore.youpiaopiao.cn")
                .contentType("application/json")
                .header(Header.USER_AGENT, " Mozilla/5.0 (iPhone; U; CPU iPhone OS 4_3_3 like Mac OS X; en-us) AppleWebKit/533.17.9 (KHTML, like Gecko) Version/5.0.2 Mobile/8J2 Safari/6533.18.5")
                .header("Referer", "https://servicewechat.com/wxc728fd458500c668/321/page-frame.html");
    }
}
